// UserInfoCollector.ts

import { UserInfo } from "./Cons";
import { L } from "./L";

type UserInfoPlatform = 'web' | 'wechat' | 'baidu' | 'bytedance' | 'native';

// 小程序API类型定义（直接内联在文件中）
type MiniProgramAPI = {
    getSystemInfoSync(): {
        brand: string;
        model: string;
        system: string;
        screenWidth: number;
        screenHeight: number;
        language: string;
    };
    getNetworkType(options?: any): Promise<{ networkType: string }>;
};

export class UserInfoCollector {
    private static _info: UserInfo = { platform: 'web' };

    static async init(): Promise<void> {
        this._info.platform = this.detectPlatform();
        
        try {
            const mp = this.getMiniProgramAPI();
            if (mp) {
                await this.collectMiniProgramInfo(mp);
            } else if (this._info.platform === 'web') {
                await this.collectWebInfo();
            } else {
                this._info.deviceName = 'Native Device';
            }
        } catch (error) {
            L.warn('[UserInfo] 收集失败:', error);
        }

        L.log(`UserInfo : ${JSON.stringify(this._info)}`);
    }

    static get userInfo(): Readonly<UserInfo> {
        return { ...this._info };
    }

    // 平台检测（动态类型检查）
    private static detectPlatform(): UserInfoPlatform {
        const globalObj = typeof window !== 'undefined' ? window : globalThis;
        
        if ((globalObj as any).wx?.getSystemInfoSync) return 'wechat';
        if ((globalObj as any).swan?.getSystemInfoSync) return 'baidu';
        if ((globalObj as any).tt?.getSystemInfoSync) return 'bytedance';
        if (typeof window !== 'undefined') return 'web';
        return 'native';
    }

    // 获取小程序API实例（带类型断言）
    private static getMiniProgramAPI(): 
        | { platform: 'wechat' | 'baidu' | 'bytedance'; api: MiniProgramAPI } 
        | null {
        
        const globalObj = typeof window !== 'undefined' ? window : globalThis;
        const wx = (globalObj as any).wx;
        const swan = (globalObj as any).swan;
        const tt = (globalObj as any).tt;

        if (wx?.getSystemInfoSync) {
            return { platform: 'wechat', api: wx };
        }
        if (swan?.getSystemInfoSync) {
            return { platform: 'baidu', api: swan };
        }
        if (tt?.getSystemInfoSync) {
            return { platform: 'bytedance', api: tt };
        }
        return null;
    }

    // 收集小程序信息（类型安全调用）
    private static async collectMiniProgramInfo(
        mp: { platform: string; api: MiniProgramAPI }
    ) {
        try {
            const sysInfo = mp.api.getSystemInfoSync();
            this._info = {
                ...this._info,
                deviceName: sysInfo.model,
                osVersion: sysInfo.system,
                screenResolution: `${sysInfo.screenWidth}x${sysInfo.screenHeight}`,
                language: sysInfo.language,
                platform: mp.platform as UserInfoPlatform
            };

            const network = await mp.api.getNetworkType();
            this._info.networkType = network.networkType;
        } catch (error) {
            L.warn(`[${mp.platform}] API调用失败:`, error);
        }
    }

    // 收集Web信息
    private static async collectWebInfo() {
        this._info.deviceName = navigator.userAgent;
        this._info.osVersion = this.parseOSVersion();
        this._info.screenResolution = `${window.screen.width}x${window.screen.height}`;
        this._info.language = navigator.language;
        this._info.timezone = Intl.DateTimeFormat().resolvedOptions().timeZone;

        try {
            this._info.ip = await this.fetchIP();
        } catch (error) {
            L.warn('IP获取失败:', error);
        }
    }

    // 其他工具方法...
    private static parseOSVersion(): string {
        const ua = navigator.userAgent;
        if (/Windows NT 10/.test(ua)) return 'Windows 10';
        if (/iPhone OS/.test(ua)) return 'iOS';
        return 'Unknown';
    }

    private static async fetchIP(): Promise<string> {
        const res = await fetch('https://api.ipify.org?format=json');
        const data = await res.json();
        return data.ip;
    }
}

// 使用示例
(async () => {
    await UserInfoCollector.init();
    L.log('用户设备:', UserInfoCollector.userInfo.deviceName);
})();